﻿using QYmall.Core.Common.Emum;
using QYmall.Core.Common.Extensions;
using QYmall.Core.Common.Helper;
using QYmall.Core.DBFactory.Database;
using QYmall.Core.IServices;
using QYmall.Core.Model.Models;
using QYmall.Core.Model.ViewModels;
using Microsoft.EntityFrameworkCore;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
using System.Threading.Tasks;

namespace QYmall.Core.Services
{
    /// <summary>
    /// 会员统计接口实现
    /// </summary>
    public class ReportMemberService : BaseService, IReportMemberService
    {
        public ReportMemberService(IDbContextFactory contentFactory) : base(contentFactory) { }

        /// <summary>
        /// 统计会员注册数量
        /// </summary>
        public async Task<IEnumerable<ReportTotalDto>> GetMemberRegisterCountAsync(int top, Expression<Func<Members, bool>> funcWhere,
            WriteRoRead writeAndRead = WriteRoRead.Read)
        {
            _context = _contextFactory.CreateContext(writeAndRead);//连接数据库
            var result = _context.Set<Members>()
                .Where(funcWhere)
                .GroupBy(x => new { x.RegTime.Month,x.RegTime.Day })
                .Select (g => new ReportTotalDto { 
                    Title = $"{g.Key.Month}月{g.Key.Day}日",
                    Total = g.Count(),
                    Amount = g.Sum(x => x.Amount)
                });
            if (top > 0) result = result.Take(top);//等于0显示所有数据
            return await result.ToListAsync();
        }

        /// <summary>
        /// 统计会员注册分页列表
        /// </summary>
        public async Task<PaginationList<Members>> GetMemberRegisterPageAsync(int pageSize, int pageIndex, Expression<Func<Members, bool>> funcWhere,
            string orderBy, WriteRoRead writeAndRead = WriteRoRead.Read)
        {
            _context = _contextFactory.CreateContext(writeAndRead);//连接数据库

            var result = _context.Set<Members>()
                .Include(x => x.User).Where(funcWhere);//条件筛选
            result = result.OrderByBatch(orderBy);//调用Linq扩展类排序
            return await PaginationList<Members>.CreateAsync(pageIndex, pageSize, result);
        }

        /// <summary>
        /// 统计会员消费金额
        /// </summary>
        public async Task<IEnumerable<ReportTotalDto>> GetMemberAmountCountAsync(int top, Expression<Func<MemberAmountLog, bool>> funcWhere,
            WriteRoRead writeAndRead = WriteRoRead.Read)
        {
            _context = _contextFactory.CreateContext(writeAndRead);//连接数据库
            var result = _context.Set<MemberAmountLog>()
                .Where(x => x.Value > 0).Where(funcWhere)
                .GroupBy(x => new { x.AddTime.Month, x.AddTime.Day })
                .Select(g => new ReportTotalDto
                {
                    Title = $"{g.Key.Month}月{g.Key.Day}日",
                    Total = g.Count(),
                    Amount = g.Sum(x => x.Value)
                });
            if (top < 0) result = result.Take(top);//等于0显示所有数据
            return await result.ToListAsync();
        }

        /// <summary>
        /// 统计会员消费分页列表
        /// </summary>
        public async Task<PaginationList<MemberAmountLog>> GetMemberAmountPageAsync(int pageSize, int pageIndex,
            Expression<Func<MemberAmountLog, bool>> funcWhere, string orderBy, WriteRoRead writeAndRead = WriteRoRead.Read)
        {
            _context = _contextFactory.CreateContext(writeAndRead);//连接数据库
            //联合查询重新组合
            var result = _context.Set<MemberAmountLog>()
                .Where(funcWhere).OrderByBatch(orderBy);//调用Linq扩展类排序
            return await PaginationList<MemberAmountLog>.CreateAsync(pageIndex, pageSize, result);
        }

        /// <summary>
        /// 统计收藏店铺会员列表
        /// </summary>
        public async Task<IEnumerable<ReportTotalDto>> GetMemberFavoriteCountAsync(int top, Expression<Func<MerchantFavorite, bool>> funcWhere,
            WriteRoRead writeAndRead = WriteRoRead.Read)
        {
            _context = _contextFactory.CreateContext(writeAndRead);//连接数据库
            var result = _context.Set<MerchantFavorite>().Where(funcWhere)
                .GroupBy(x => new { x.AddTime.Month, x.AddTime.Day })
                .Select(g => new ReportTotalDto
                {
                    Title = $"{g.Key.Month}月{g.Key.Day}日",
                    Total = g.Count(),
                    Amount = 0
                });
            if (top < 0) result = result.Take(top);//等于0显示所有数据
            return await result.ToListAsync();
        }
    }
}
